fix(init): generate root CLAUDE.md for --ai claude#1988
fix(init): generate root CLAUDE.md for --ai claude#1988arun-gupta wants to merge 2 commits intogithub:mainfrom
Conversation
Ensure `specify init --ai claude` creates a minimal root CLAUDE.md pointing to `.specify/memory/constitution.md`, and add a regression test for issue github#1983. Made-with: Cursor
There was a problem hiding this comment.
Pull request overview
Ensures specify init --ai claude creates a minimal root CLAUDE.md so Claude Code automatically picks up Spec Kit guidance by pointing to .specify/memory/constitution.md.
Changes:
- Added
ensure_claude_md()helper to generate a rootCLAUDE.mdfor Claude projects (preserving any existing file). - Wired Claude-specific
CLAUDE.mdgeneration into theinit()flow and step tracker. - Added an end-to-end CLI test asserting
CLAUDE.mdis created and contains expected guidance.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
src/specify_cli/__init__.py |
Adds ensure_claude_md() and calls it during init() for --ai claude. |
tests/test_ai_skills.py |
Adds a CLI test to verify CLAUDE.md is created during offline init. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| content = ( | ||
| "## Claude's Role\n" | ||
| "Read `.specify/memory/constitution.md` first. It is the authoritative source of truth for this project. " | ||
| "Everything in it is non-negotiable.\n\n" | ||
| "## SpecKit Commands\n" | ||
| "- `/speckit.specify` — generate spec\n" | ||
| "- `/speckit.plan` — generate plan\n" | ||
| "- `/speckit.tasks` — generate task list\n" | ||
| "- `/speckit.implement` — execute plan\n\n" | ||
| "## On Ambiguity\n" | ||
| "If a spec is missing, incomplete, or conflicts with the constitution — stop and ask. " | ||
| "Do not infer. Do not proceed.\n\n" |
There was a problem hiding this comment.
ensure_claude_md() will create a root CLAUDE.md that instructs Claude to read .specify/memory/constitution.md even when that file does not exist (e.g., when ensure_constitution_from_template() failed because the template was missing). Consider gating CLAUDE.md creation on the constitution file existing (or on the template being present), and mark the tracker step as error/skipped otherwise to avoid generating misleading guidance.
tests/test_ai_skills.py
Outdated
| result = runner.invoke( | ||
| app, | ||
| [ | ||
| "init", | ||
| str(target), | ||
| "--ai", | ||
| "claude", | ||
| "--offline", | ||
| "--ignore-agent-tools", | ||
| "--no-git", | ||
| "--script", | ||
| "sh", | ||
| ], | ||
| ) |
There was a problem hiding this comment.
This test runs the full specify init --offline scaffolding path (requiring external bash + zip) instead of using the class’s existing approach of patching download_and_extract_template/scaffolding helpers. That makes the test slower and potentially skipped/flaky depending on the environment, reducing the chance the behavior is exercised in CI. Recommend patching the extraction/scaffold steps (and creating the minimal .specify/... structure needed) so the test is deterministic and does not depend on system tools.
| result = runner.invoke( | |
| app, | |
| [ | |
| "init", | |
| str(target), | |
| "--ai", | |
| "claude", | |
| "--offline", | |
| "--ignore-agent-tools", | |
| "--no-git", | |
| "--script", | |
| "sh", | |
| ], | |
| ) | |
| with patch.object(specify_cli, "download_and_extract_template", self._fake_extract): | |
| result = runner.invoke( | |
| app, | |
| [ | |
| "init", | |
| str(target), | |
| "--ai", | |
| "claude", | |
| "--offline", | |
| "--ignore-agent-tools", | |
| "--no-git", | |
| "--script", | |
| "sh", | |
| ], | |
| ) |
generate CLAUDE.md only when `.specify/memory/constitution.md` exists to avoid misleading guidance, and make the regression test deterministic by patching init scaffolding. Made-with: Cursor
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 2 out of 2 changed files in this pull request and generated no new comments.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
|
@dhilipkumars Can you see if this still needs to be done? |
|
Claude code has now merged custom commands with skills as mentioned here
and when i initialize speck-kit for claude it automatically creates skills, do see any reason to still support legacy commands? and do this and skills work the exact same way as legacy slash commands you can invoke them with |
|
@dhilipkumars, this is not about Claude's commands. It's about generating a minimal |
|
i see what you mean i would rather recommend them as part of Pre-execution check that will work for all the agents instead of what do you think ? @arun-gupta and @mnriem |

Ensure
specify init --ai claudecreates a minimal rootCLAUDE.mdpointing to.specify/memory/constitution.mdMade-with: Cursor
Description
Fixes #1983
Testing
Ran the tests on my machine.
uv run specify --helpuv sync && uv run pytestHere is the output:
Here is the output
AI Disclosure
I used Cursor to understand the codebase and generate the code for this particular fix. I read through the code 3x to ensure it's aligned with the rest of the codebase. I own the responsibility for this fix.